home *** CD-ROM | disk | FTP | other *** search
/ Cream of the Crop 1 / Cream of the Crop 1.iso / PROGRAM / CBASE102.ARJ / BFLPUSH.C < prev    next >
Text File  |  1991-09-23  |  4KB  |  149 lines

  1. /*    Copyright (c) 1989 Citadel    */
  2. /*       All Rights Reserved        */
  3.  
  4. /* #ident    "@(#)bflpush.c    1.5 - 91/09/23" */
  5.  
  6. #include <ansi.h>
  7.  
  8. /* ansi headers */
  9. #include <errno.h>
  10. #ifdef AC_STDDEF
  11. #include <stddef.h>
  12. #endif
  13. #ifdef AC_STDLIB
  14. #include <stdlib.h>
  15. #endif
  16. #ifdef AC_STRING
  17. #include <string.h>
  18. #endif
  19.  
  20. /* local headers */
  21. #include "blkio_.h"
  22.  
  23. /*man---------------------------------------------------------------------------
  24. NAME
  25.      bflpush - push block onto free list
  26.  
  27. SYNOPSIS
  28.      #include <blkio.h>
  29.  
  30.      int bflpush(bp, bnp)
  31.      BLKFILE *bp;
  32.      const bpos_t *bnp;
  33.  
  34. DESCRIPTION
  35.      The bflpush function puts the block number pointed to by bnp into
  36.      the free list of the block file associated with BLKFILE pointer
  37.      bp.  If the value pointed to by bnp is one block past the end of
  38.      the file, it is accepted but not actually added to the list.
  39.  
  40.      bflpush will fail if one or more of the following is true:
  41.  
  42.      [EINVAL]       bp is not a valid BLKFILE pointer.
  43.      [EINVAL]       bnp is the NULL pointer.
  44.      [EINVAL]       bnp points to a value less than 1.
  45.      [BEEOF]        bp is empty.
  46.      [BEEOF]        bnp points to a value farther than one block past
  47.                     the end of file.
  48.      [BENFL]        bp does not have a free list.
  49.      [BENOPEN]      bp is not open for writing.
  50.  
  51. SEE ALSO
  52.      bflpop.
  53.  
  54. DIAGNOSTICS
  55.      Upon successful completion, a value of 0 is returned.  Otherwise,
  56.      a value of -1 is returned, and errno set to indicate the error.
  57.  
  58. NOTES
  59.      To use the free list functions in the blkio library, the first
  60.      element of the file header must be the free list head with type
  61.      bpos_t.  This must be initialized to 0 immediately after the file
  62.      is created and not accessed afterward except using bflpush and
  63.      bflpush.  Also, the block size must be at least sizeof(bpos_t).
  64.  
  65. ------------------------------------------------------------------------------*/
  66. #ifdef AC_PROTO
  67. int bflpush(BLKFILE *bp, const bpos_t *bnp)
  68. #else
  69. int bflpush(bp, bnp)
  70. BLKFILE *bp;
  71. const bpos_t *bnp;
  72. #endif
  73. {
  74.     bpos_t    oldflhno = 0;    /* old free list head number */
  75.     bpos_t    newflhno = 0;    /* new free list head number */
  76.     void *    buf    = NULL;
  77.  
  78.     /* validate arguments */
  79.     if (!b_valid(bp) || bnp == NULL) {
  80.         errno = EINVAL;
  81.         return -1;
  82.     }
  83.     if (*bnp < 1) {
  84.         errno = EINVAL;
  85.         return -1;
  86.     }
  87.  
  88.     /* check if not open */
  89.     if (!(bp->flags & BIOWRITE)) {
  90.         errno = BENOPEN;
  91.         return -1;
  92.     }
  93.  
  94.     /* check if no free list */
  95.     if (bp->hdrsize < sizeof(oldflhno) || bp->blksize < sizeof(oldflhno)) {
  96.         errno = BENFL;
  97.         return -1;
  98.     }
  99.  
  100.     /* check if header not yet written */
  101.     if (bp->endblk < 1) {
  102.         errno = BEEOF;
  103.         return -1;
  104.     }
  105.  
  106.     /* check if block past endblk */
  107.     if (*bnp > bp->endblk) {
  108.         errno = BEEOF;
  109.         return -1;
  110.     }
  111.  
  112.     /* check if block is endblk */
  113.     if (*bnp == bp->endblk) {
  114.         return 0;
  115.     }
  116.  
  117.     /* get block number of current free list head */
  118.     if (bgethf(bp, (size_t)0, &oldflhno, sizeof(oldflhno)) == -1) {
  119.         BEPRINT;
  120.         return -1;
  121.     }
  122.  
  123.     /* link to rest of free list */
  124.     newflhno = *bnp;
  125.     buf = calloc((size_t)1, bp->blksize);
  126.     if (buf == NULL) {
  127.         BEPRINT;
  128.         errno = ENOMEM;
  129.         return -1;
  130.     }
  131.     memcpy(buf, &oldflhno, sizeof(oldflhno));
  132.     if (bputb(bp, newflhno, buf) == -1) {
  133.         BEPRINT;
  134.         free(buf);
  135.         buf = NULL;
  136.         return -1;
  137.     }
  138.     free(buf);
  139.     buf = NULL;
  140.  
  141.     /* write new free list head number to header */
  142.     if (bputhf(bp, (size_t)0, &newflhno, sizeof(newflhno)) == -1) {
  143.         BEPRINT;
  144.         return -1;
  145.     }
  146.  
  147.     return 0;
  148. }
  149.